package offer;

import binaryTree.basic.TreeNode;

import java.util.LinkedList;
import java.util.Queue;

public class Offer37 {


    public class Codec {

        // Encodes a tree to a single string.
        public String serialize(TreeNode root) {
            Queue<TreeNode> queue = new LinkedList<>();
            if (root == null) {
                return "]";
            }
            StringBuffer stringBuffer = new StringBuffer("[");
            queue.add(root);
//           todo:上面不太对 正确的做法
//           while (!queue.isEmpty()){
//               TreeNode cur = queue.poll();
//               if (cur.left!=null){
//                   queue.add(cur.left);
//               }else {
//                   queue.add(new TreeNode(-1));
//               }
//               if (cur.right!=null){
//                   queue.add(cur.right);
//               }else{
//                   queue.add(new TreeNode(-1));
//               }
//           }
            //todo:简单明了
            while (!queue.isEmpty()) {
                TreeNode cur = queue.poll();
                if (cur != null) {
                    stringBuffer.append(cur.val + ",");
                    queue.add(cur.left);
                    queue.add(cur.right);
                } else {
                    stringBuffer.append("null" + ",");
                }

            }

            return stringBuffer.toString();


        }

        // Decodes your encoded data to tree.
        public TreeNode deserialize(String data) {
            if (data.equals("[]")){
                return  null;
            }
            String[] vals = data.substring(1, data.length() - 1).split(",");
            TreeNode root = new TreeNode(Integer.valueOf(vals[0]));
           Queue<TreeNode>  queue = new LinkedList<>();
           queue.add(root);
           int i=1;
           while (!queue.isEmpty()){
             TreeNode  cur= queue.poll();
             //todo: 与序列化不同的是这里的 判断是否为空转向判断序列化后的数组是否为空  之前是判断加入的节点是否为空
//               todo: 当数组的位置上的元素不为空的时候  就初始化节点 当为空的时候 就不做处理直接数组元素位置加一
             if (!vals[i].equals("null")){
                 cur.left=new TreeNode(Integer.valueOf(vals[i]));
//                 todo:将节点元素加入到队列中
                 queue.add(cur.left);
             }
             i++;
             if (!vals[i].equals("null")){
                 cur.right=new TreeNode(Integer.valueOf(vals[i]));
                 queue.add(cur.right);
             }
             i++;
           }
           return  root;
        }


        public String serialize1(TreeNode root) {
            if (root == null) return "[]";
            StringBuilder res = new StringBuilder("[");
            Queue<TreeNode> queue = new LinkedList();
            queue.add(root);
            while (!queue.isEmpty()) {
                TreeNode node = queue.poll();
//                todo:这样的方式避免了空指针异常
                if (node != null) {
                    res.append(node.val + ",");
                    queue.add(node.left);
                    queue.add(node.right);
                } else res.append("null,");
            }
            return res.toString();
        }

        // Decodes your encoded data to tree.
        public TreeNode deserialize2(String data) {
            if (data.equals("[]")) return null;
            String[] vals = data.substring(1, data.length() - 1).split(",");
            TreeNode root = new TreeNode(Integer.parseInt(vals[0]));
            Queue<TreeNode> queue = new LinkedList();
            queue.add(root);
            int i = 1;
            while (!queue.isEmpty()) {
                TreeNode node = queue.poll();
                if (!vals[i].equals("null")) {
                    node.left = new TreeNode(Integer.parseInt(vals[i]));
                    queue.add(node.left);
                }
                i++;
                if (!vals[i].equals("null")) {
                    node.right = new TreeNode(Integer.parseInt(vals[i]));
                    queue.add(node.right);
                }
                i++;
            }
            return root;
        }
    }




    public static void main(String[] args) {

        TreeNode treeNode1 = new TreeNode(1);
        TreeNode treeNode2 = new TreeNode(2);
        TreeNode treeNode3 = new TreeNode(3);
        TreeNode treeNode4 = new TreeNode(4);
        TreeNode treeNode5 = new TreeNode(5);
        treeNode1.left=treeNode2;
        treeNode1.right=treeNode3;
        treeNode2.left=treeNode4;
        treeNode2.right=treeNode5;

        Offer37 offer37 = new Offer37();
        Codec codec = offer37.new Codec();
//        System.out.println(codec.serialize(treeNode1));
        System.out.println(codec.serialize1(treeNode1));
        System.out.println(codec.deserialize2("[]"));




    }


}
